try:
    import gtk
    import gtk.glade
except: sys.exit(1)

import sys,os
import runtime
import gobject
import game
from pygame.locals import *
from GUI.constants import *

def find_item_name(dic,item):
    a = [name for name in dic.keys() if dic[name] == item]
    if not len(a) == 1:
        return None
    else:
        return a[0]


class gtk_helper(object):

    def get_widget(self,name):
        return self.wTree.get_widget(name)

    def show_popup(self,name,event):
        """pops up a menu - e.g. on right click"""
        self.get_widget(name).popup(None, None, None
        		, event.button, event.time)


class main_window_events(gtk_helper):
    """not runnable by itself 
       - inherit from it for the sake of code clarity
    """

    def treeview_click(self,widget=None,event=None):
        if event.button == 3:
            self.show_popup("popup_edit",event)

    def new_item_from_treeview(self,event):
        selection = self.get_widget("treeview1").get_selection()
        model,sel_iter = selection.get_selected()

        obj = model.get_value(sel_iter, 0)
        # TODO: Pop up a "Are you sure" dialogue
        try:
            if obj.objtype == "Gameobject":
                self.new_game_object()
            elif obj.objtype == "Sprite":
                # TODO
                pass
            elif obj.objtype == "Gamescreen":
                self.new_game_screen()
            elif obj.objtype == "Workstate":
                self.new_workstate()

            self.treeviewhelp.update_item_list()
        except Exception, inst:
            objtype=model.get_value(sel_iter,2)
            if objtype == "gamescreens":
                self.new_game_screen()
            elif objtype == "workstates":
                self.new_workstate()
            elif objtype == "gameobjects":
                self.new_game_object()
            pass

    def add_new_event(self,event):

        if not self.selectedworkstate.actions.has_key(event):
            self.selectedworkstate.actions[event] = "\n"
            cb = self.get_widget("cbxworkstateevents")
            model = cb.get_model()
            model.append([event_names.get(event,str(event)),event])
            cb.set_model(model)
            self.change_event_selected()


    def show_new_event_popup(self,widget=None,event=None):
        self.show_popup("popup_events",event)

    def show_item_popup(self,widget=None,event=None):
        self.show_popup("popup_edit",event)

    def show_game_properties(self,widget=None):
        """Show the Game Properties window"""
        self.get_widget("wnd_game").show()
        self.get_widget("txt_game_name").set_text(str(self.game.title))
        self.get_widget("txt_initial_gamescreen").set_text(str(self.game.startscreen))

        text = self.get_widget("textview_load_events")
        textbuffer = text.get_buffer()
        try:
            textbuffer.set_text(self.game.initcode)
        except: pass

        # TODO : 
        # Populate the selection box

    def new_game(self,widget=None):
        self.game = game.Game("")
        self.show_game_properties()
        self.treeviewhelp.clear()
        self.treeviewhelp.populate_from_game(self.game)


    def game_properties_ok(self,widget=None):
        self.game.title = self.get_widget("txt_game_name").get_text()
        self.get_widget("wnd_main").set_title(self.game.title + " - Game Baker")
        self.get_widget("wnd_game").hide()
        self.game.startscreen = self.get_widget("txt_initial_gamescreen").get_text() 
        if not self.game.gamescreens.has_key(self.game.startscreen):    
            self.game.gamescreens[self.game.startscreen] = self.game.gamescreen((800,600),self.game.startscreen)
        text = self.get_widget("textview_load_events")
        textbuffer = text.get_buffer()
        startiter, enditer = textbuffer.get_bounds()
        self.game.initcode = textbuffer.get_text(startiter,enditer)
        self.treeviewhelp.update_item_list()

    def object_ok(self,widget=None):
        oldname = find_item_name(self.game.gameobjects,self.selectedobject)
        newname = self.get_widget("txt_obj_name").get_text()
        if not oldname == newname:
            self.game.gameobjects[newname] = self.selectedobject
            del self.game.gameobjects[oldname]
            self.selectedobject.name = newname
        self.treeviewhelp.update_item_list()

        if not self.get_widget("txt_obj_sprite").get_text()=="":
            self.selectedobject.sprite = self.get_widget("txt_obj_sprite").get_text()
        else:
            self.selectedobject.sprite = None

        # Change Workstate
        cb = self.get_widget("cbx_workstateoptns")
        try:
            self.selectedobject.baseworkstate= str(cb.get_model()[cb.get_active()][0])
        except: pass

        self.get_widget("wnd_Object").hide()

    def gamescreen_ok(self,widget=None):
        oldname = find_item_name(self.game.gamescreens,self.selectedgamescreen)
        newname = self.get_widget("txt_gamescreen_name").get_text()
        if not oldname == newname:
            self.game.gamescreens[newname] = self.selectedgamescreen
            del self.game.gamescreens[oldname]
            self.treeviewhelp.update_item_list()

        r = int( self.get_widget("txt_gamescreen_bg_r").get_text() )
        g = int( self.get_widget("txt_gamescreen_bg_g").get_text() )
        b = int( self.get_widget("txt_gamescreen_bg_b").get_text() )
        self.selectedgamescreen.color  = (r,g,b)
        # Itterate through list and update startobjects
        treeview =  self.get_widget("treeview_gamescreen_objects")
        model = treeview.get_model()

        # Need TODO - change this so it stores a string, not a reference (in engine too)
        startobjects = [m[0] for m in model]
        self.selectedgamescreen.startobjects = startobjects


        self.get_widget("wnd_gamescreen").hide()

    def gamescreen_delete_initial_object(self,widget=None):
        treeview =  self.get_widget("treeview_gamescreen_objects")
        #model = treeview.get_model()
        selection = treeview.get_selection()
        model,sel_iter = selection.get_selected()

        if not sel_iter is None:
            del model[sel_iter]


    def workstate_ok(self,widget=None):
        oldname = find_item_name(self.game.workstates,self.selectedworkstate)
        newname = self.get_widget("txt_workstate_name").get_text()
        if not oldname == newname:
            self.game.workstates[newname] = self.selectedworkstate
            del self.game.workstates[oldname]
        # Still have to update treeview
        self.treeviewhelp.update_item_list()

        inherits = self.get_widget("txt_workstate_inherits").get_text()
        if inherits == "":
            self.selectedworkstate.inherits = None
        else:
            self.selectedworkstate.inherits = inherits

        self.get_widget("wnd_workstate").hide()


    def workstate_cancel(self,widget=None):
        self.get_widget("wnd_workstate").hide()


    def change_event_selected(self,widget=None):
        cb = self.get_widget("cbxworkstateevents")
        active = cb.get_active()
        model = cb.get_model()

        text = self.get_widget("text_event_script")
        textbuffer = text.get_buffer()

        textbuffer.set_text(self.selectedworkstate.actions.get(int(model[active][1]),""))

    def save_event(self,widget=None):
        cb = self.get_widget("cbxworkstateevents")
        active = cb.get_active()
        model = cb.get_model()

        text = self.get_widget("text_event_script")
        textbuffer = text.get_buffer()
        startiter, enditer = textbuffer.get_bounds()
        script = textbuffer.get_text(startiter,enditer)
        self.selectedworkstate.actions[int(model[active][1])] = script

    def choose_background_colour_gamescreen(self,widget=None):
        # Show Colour Selection
        colorseldlg = gtk.ColorSelectionDialog("Background Colour")

        # Get the ColorSelection widget
        colorsel = colorseldlg.colorsel
        colorsel.set_has_opacity_control(False)

        try:
            colour = self.selectedgamescreen.color
        except:
            colour = (255,255,255)

        gdkcolour = gtk.gdk.Color()

        gdkcolour.red = colour[0] *65535 / 255
        gdkcolour.green = colour[1]*65535 / 255
        gdkcolour.blue = colour[2]*65535 / 255
        colorsel.set_current_color(gdkcolour)

        self.gdkcolour = gdkcolour
        def change_colour(widget = None):
            self.gdkcolour = colorsel.get_current_color()

        colorsel.connect("color_changed", change_colour)

        response = colorseldlg.run()
        gdkcolour = self.gdkcolour

        if response -- gtk.RESPONSE_OK:
            self.get_widget("txt_gamescreen_bg_r").set_text(str(gdkcolour.red * 255 / 65535))
            self.get_widget("txt_gamescreen_bg_g").set_text(str(gdkcolour.green* 255 / 65535))
            self.get_widget("txt_gamescreen_bg_b").set_text(str(gdkcolour.blue* 255 / 65535))
        else:
            pass

        colorseldlg.hide()



    def delete_item(self,widget=None,prop2 = None, prop3 = None):
        selection = self.get_widget("treeview1").get_selection()
        model,sel_iter = selection.get_selected()

        obj = model.get_value(sel_iter, 0)
        # To Do: Pop up a "Are you sure" dialogue
        try:
            if obj.objtype == "Gameobject":
                self.delete_gameobject(obj)
            elif obj.objtype == "Sprite":
                self.delete_sprite(obj)
            elif obj.objtype == "Gamescreen":
                self.delete_gamescreen(obj)
            elif obj.objtype == "Workstate":
                self.delete_workstate(obj)

            self.treeviewhelp.update_item_list()
        except Exception, inst:
            pass


    def open_properties(self,widget=None,prop2 = None, prop3 = None):
        selection = self.get_widget("treeview1").get_selection()
        model,sel_iter = selection.get_selected()

        obj = model.get_value(sel_iter, 0)
        try:
            if obj.objtype == "Gameobject":
                self.get_widget("wnd_Object").show()
                # Set Name
                self.get_widget("txt_obj_name").set_text(find_item_name(self.game.gameobjects,obj))

                if not obj.sprite is None:
                    self.get_widget("txt_obj_sprite").set_text(obj.sprite)

                model = gtk.ListStore(str)
                for ws in self.game.workstates.keys():
                    model.append([ws])
                cb = self.get_widget("cbx_workstateoptns")
                cb.set_model(model)
                try:
                    cb.set_active(self.game.workstates.keys().index(obj.baseworkstate))
                except: pass
                self.selectedobject = obj


            elif obj.objtype == "Sprite":
                pass

            elif obj.objtype == "Gamescreen":
                self.get_widget("wnd_gamescreen").show()
                self.get_widget("txt_gamescreen_name").set_text(find_item_name(self.game.gamescreens,obj))
                try: 
                    color = obj.color
                except:
                    color=(255,255,255)

                self.get_widget("txt_gamescreen_bg_r").set_text( str(color[0]) )
                self.get_widget("txt_gamescreen_bg_g").set_text( str(color[1]) )
                self.get_widget("txt_gamescreen_bg_b").set_text( str(color[2]) )

                # Show List of options for objects
                model = gtk.ListStore(str)
                for go in self.game.gameobjects.keys():
                    model.append([go])
                cb = self.get_widget("cbx_gamescreen_object_options")
                cb.set_model(model)

                self.selectedgamescreen = obj


                treeview =  self.get_widget("treeview_gamescreen_objects")
                treestore = gtk.TreeStore(gobject.TYPE_PYOBJECT, gobject.TYPE_STRING,gobject.TYPE_STRING)

                for go in obj.startobjects:
                    insert_iter = treestore.append(None, [go,go.name,go.name])
                treeview.set_model(treestore)


            elif obj.objtype == "Workstate":
                self.get_widget("wnd_workstate").show()
                self.get_widget("txt_workstate_name").set_text(find_item_name(self.game.workstates,obj))

                if obj.inherits is not None:
                    self.get_widget("txt_workstate_inherits").set_text(obj.inherits)
                else:
                    self.get_widget("txt_workstate_inherits").set_text("")

                cb = self.get_widget("cbxworkstateevents")

                model = gtk.ListStore(str,int)
                model.clear()
                for event in obj.actions.keys():
                    model.append([event_names.get(event,str(event)),event])

                cb.set_model(model)

                cb.set_active(0)
                self.selectedworkstate = obj
                self.change_event_selected()
                

        except Exception, inst:
            print inst

    def add_obj_to_gamescreen(self,widget=None):
        # Get current selection
        cb =  self.get_widget("cbx_gamescreen_object_options")
        active = cb.get_active()
        model = cb.get_model()
        obj_name = model[active][0]

        # Now add this to the list        
        treeview =  self.get_widget("treeview_gamescreen_objects")
        model = treeview.get_model()
        obj = self.game.gameobjects[obj_name]
        model.append(None,[obj,obj_name,obj_name])

    def add_item_choice(self,widget=None):
        self.get_widget("wnd_new_item").show()

    def import_sprite(self,widget=None):
        file_open = gtk.FileChooserDialog(title="Open Game File"
                                , action=gtk.FILE_CHOOSER_ACTION_OPEN
                                , buttons=(gtk.STOCK_CANCEL
                                                , gtk.RESPONSE_CANCEL
                                                , gtk.STOCK_OPEN
                                                , gtk.RESPONSE_OK))
        """Create and add the filter"""
        filter = gtk.FileFilter()
        filter.set_name("Game Baker Sprite")
        filter.add_pattern("*.gbs")
        file_open.add_filter(filter)
        """Create and add the 'all files' filter"""
        filter = gtk.FileFilter()
        filter.set_name("All files")
        filter.add_pattern("*")
        file_open.add_filter(filter)
        filename = ""
        if file_open.run() == gtk.RESPONSE_OK:
                filename = file_open.get_filename()
        file_open.destroy()
 
        self.import_external_sprite(filename)

        self.treeviewhelp.update_item_list()
        

    def open_file(self,widget = None):
        file_open = gtk.FileChooserDialog(title="Open Game File"
                                , action=gtk.FILE_CHOOSER_ACTION_OPEN
                                , buttons=(gtk.STOCK_CANCEL
                                                , gtk.RESPONSE_CANCEL
                                                , gtk.STOCK_OPEN
                                                , gtk.RESPONSE_OK))
        """Create and add the filter"""
        filter = gtk.FileFilter()
        filter.set_name("Game Baker Games")
        filter.add_pattern("*.gb")
        file_open.add_filter(filter)
        """Create and add the 'all files' filter"""
        filter = gtk.FileFilter()
        filter.set_name("All files")
        filter.add_pattern("*")
        file_open.add_filter(filter)
        filename = ""
        if file_open.run() == gtk.RESPONSE_OK:
            filename = file_open.get_filename()
        file_open.destroy()
	
        if not filename == "":
            import gbfileio
            self.game = gbfileio.loadgame(filename)
            self.treeviewhelp.clear()
            self.treeviewhelp.populate_from_game(self.game)
            self.filename = filename
            os.chdir(os.path.split(filename)[0])
            self.get_widget("wnd_main").set_title(self.game.title + " - Game Baker")

    def closegame(self,widget=None):
        """Close the currently open game"""
        self.treeviewhelp.clear()
        self.game=None
        self.get_widget("wnd_main").set_title("- Game Baker")

    def save_file(self,widget = None):
        if self.filename == "":
            self.save_file_as(widget)
        else:
            import gbfileio
            gbfileio.savegame(self.filename,self.game)

    def save_file_as(self,widget = None):
        file_save = gtk.FileChooserDialog(title="Save Game File"
                                , action=gtk.FILE_CHOOSER_ACTION_SAVE
                                , buttons=(gtk.STOCK_CANCEL
                                    , gtk.RESPONSE_CANCEL
                                    , gtk.STOCK_SAVE
                                    , gtk.RESPONSE_OK))
        """Create and add the filter"""
        filter = gtk.FileFilter()
        filter.set_name("Game Baker Game")
        filter.add_pattern("*.gb")
        file_save.add_filter(filter)
        """Create and add the 'all files' filter"""
        filter = gtk.FileFilter()
        filter.set_name("All files")
        filter.add_pattern("*")
        file_save.add_filter(filter)
        filename = ""
        if file_save.run() == gtk.RESPONSE_OK:
            filename = file_save.get_filename()
            if not filename[-3:] == ".gb":
                filename = filename + ".gb"
        file_save.destroy()

        if not filename == "":
            import gbfileio
            gbfileio.savegame(filename,self.game)
            os.chdir(os.path.split(filename)[0])
            self.filename = filename

    def new_game_object(self,widget = None):
        count = 1
        while self.game.gameobjects.has_key("GameObject%d"%count):
            count+=1
        mytestGameObject = self.game.gameobject("GameObject%d"%count)
        # Hide options window if it's shown
        self.get_widget("wnd_new_item").hide()
        self.treeviewhelp.update_item_list()
        
    def new_workstate(self,widget = None):
        count = 1
        while self.game.workstates.has_key("Workstate%d"%count):
            count+=1
        mytestWorkState = self.game.workstate("Workstate%d"%count)
        #Hide options window if it's shown
        self.get_widget("wnd_new_item").hide()
        self.treeviewhelp.update_item_list()

    def new_game_screen(self,widget=None):
        count = 1
        while self.game.gamescreens.has_key("GameScreen%d"%count):
            count+=1
        mytestGameScreen = self.game.gamescreen((800,600),"GameScreen%d"%count)
        #Hide options window if it's shown
        self.get_widget("wnd_new_item").hide()    
        self.treeviewhelp.update_item_list()    
